/*This source code copyrighted by Lazy Foo' Productions (2004-2013)
 and may not be redistributed without written permission.*/

//The headers
#include "SDL/SDL.h"
#include "SDL/SDL_image.h"

#include "Globals.h"
#include "Tile.h"
#include "Dot.h"
#include "Timer.h"
#include "Level.h"

#include <string>

bool init() {
	//Initialize all SDL subsystems
	if (SDL_Init(SDL_INIT_EVERYTHING) == -1) {
		return false;
	}

	//Set up the screen
	screen = SDL_SetVideoMode(SCREEN_WIDTH, SCREEN_HEIGHT, SCREEN_BPP,
			SDL_SWSURFACE);

	//If there was an error in setting up the screen
	if (screen == NULL) {
		return false;
	}

	//Set the window caption
	SDL_WM_SetCaption("The Travelers", NULL);

	//If everything initialized fine
	return true;
}

void clean_up() {
	//Free the surfaces
	SDL_FreeSurface(dot);
	SDL_FreeSurface(tileSheet);

	//Free the tiles
	for (int t = 0; t < TOTAL_TILES; t++) {
		delete tiles[t];
	}

	//Quit SDL
	SDL_Quit();
}

SDL_Surface *load_image(std::string filename) {
	//The image that's loaded
	SDL_Surface* loadedImage = NULL;

	//The optimized surface that will be used
	SDL_Surface* optimizedImage = NULL;

	//Load the image
	loadedImage = IMG_Load(filename.c_str());

	//If the image loaded
	if (loadedImage != NULL) {
		//Create an optimized surface
		optimizedImage = SDL_DisplayFormat(loadedImage);

		//Free the old surface
		SDL_FreeSurface(loadedImage);

		//If the surface was optimized
		if (optimizedImage != NULL) {
			//Color key surface
			SDL_SetColorKey(optimizedImage, SDL_SRCCOLORKEY,
					SDL_MapRGB(optimizedImage->format, 0, 0xFF, 0xFF));
		}
	}

	//Return the optimized surface
	return optimizedImage;
}

bool load_files() {
	//Load the dot image
	dot = load_image("/home/nick/code/Media/Sprites/dot.png");

	//If there was a problem in loading the dot
	if (dot == NULL) {
		return false;
	}

	//Load the tile sheet
	tileSheet = load_image("/home/nick/code/Media/Map/tiles.png");

	//If there was a problem in loading the tiles
	if (tileSheet == NULL) {
		return false;
	}

	//If everything loaded fine
	return true;
}

int main(int argc, char* args[]) {
	//Quit flag
	bool quit = false;

	//The dot
	Dot * myDot = new Dot();;

	//The frame rate regulator
	Timer fps;

	//Initialize
	if (init() == false) {
		return 1;
	}

	//Load the files
	if (load_files() == false) {
		return 1;
	}

	//Clip the tile sheet
	clip_tiles();

	//Set the tiles
	if (set_tiles(tiles) == false) {
		return 1;
	}

	//While the user hasn't quit960
	while (quit == false) {
		//Start the frame timer
		fps.start();

		//While there's events to handle
		while (SDL_PollEvent(&event)) {
			//Handle events for the dot
			myDot->handleInput();

			//If the user has Xed out the window
			if (event.type == SDL_QUIT) {
				//Quit the program
				quit = true;
			}
		}

		//Move the dot
		myDot->move(tiles);

		//Set the camera
		myDot->set_camera();

		//Show the tiles
		for (int t = 0; t < TOTAL_TILES; t++) {
			if (tiles[t]->isWithin(camera->x, camera->y)) {
				//Show the tile
				tiles[t]->show((tiles[t]->getX() - camera->x),
						(tiles[t]->getY() - camera->y), tileSheet, screen,
						clips[tiles[t]->getType()]);
			}

			//Show the dot on the screen
			myDot->show(myDot->getX() - camera->x, myDot->getY() - camera->y,
					dot, screen, camera);

			//Update the screen
			if (SDL_Flip(screen) == -1) {
				return 1;
			}

			//Cap the frame rate
			if (fps.get_ticks() < 1000 / FRAMES_PER_SECOND) {
				SDL_Delay((1000 / FRAMES_PER_SECOND) - fps.get_ticks());
			}
		}

		//Clean up
		clean_up();

		return 0;
	}
}
